package server.storage;

import static org.junit.Assert.fail;

import org.junit.After;
import org.junit.AfterClass;
import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;

import server.controller.AccessControlMain;
import server.controller.FacultyUser;
import server.controller.GuestUser;
import server.controller.HandicappedUser;
import server.controller.ParkingUser;
import server.controller.StudentUser;
import client.parkingdisplay.SpotDisplay;


public class ParkedUsersTest {
	
	static Thread access_control_main_thread;
	static ParkedUsers parked_users;
	
	static int sleep_time= 1000;

	@BeforeClass
	public static void setUpBeforeClass() throws Exception {
		access_control_main_thread= new Thread(
	            new Runnable() {
	                public void run() {
	                    AccessControlMain.main(null);
	                }
	            });
			access_control_main_thread.start();
			Thread.sleep(sleep_time);
			
			parked_users= ParkedUsers.instance("garage.txt");
	}

	@AfterClass
	public static void tearDownAfterClass() throws Exception {
		//access_control_main_thread.stop();
	}

	@Before
	public void setUp() throws Exception {
		
	}

	@After
	public void tearDown() throws Exception {
		
	}
	
	private void testSearchParkingSpot_util_001(String spot_number, ParkingUser parking_user, boolean should_fail)
	{
		Thread spot= null;
		
		if(spot_number== null)
			should_fail= true;
		else
		{
			spot = new SpotDisplay("localhost", 3738, spot_number);
			spot.start();
        
	        try
	        {
	        	Thread.sleep(sleep_time);
	        }
			catch(InterruptedException e)
			{
				fail("InterruptedException thrown during Thread.sleep()");
			}
		}
		
        ParkingSpot parking_spot= parked_users.searchParkingSpot(parking_user);
        
        //if(spot!= null)
        //	spot.stop();
        
        
        if(should_fail)
        {
        	if(parking_spot!= null)
        		fail("Parking spot was found, but should not have been.");
        	
        	return;        		
        }
        
        if(parking_spot== null)
        		fail("Parking spot was not found");

        if(!parking_spot.getParkingType().equals(parking_user.toString()))
        	fail("Parking spot returned is not of correct type");
	}

	@Test
	public void testSearchParkingSpot_001() {
		testSearchParkingSpot_util_001("315", new StudentUser("Jane", "0"), false);
	}
	
	@Test
	public void testSearchParkingSpot_002() {
		testSearchParkingSpot_util_001("101", new FacultyUser("Jane", "0"), false);
	}
	
	@Test
	public void testSearchParkingSpot_003() {
		testSearchParkingSpot_util_001("120", new HandicappedUser(), false);
	}
	
	@Test
	public void testSearchParkingSpot_004() {
		testSearchParkingSpot_util_001("139", new GuestUser(), false);
	}
	
	@Test
	public void testSearchParkingSpot_005() {
		ParkingSpot parking_spot= parked_users.searchParkingSpot(new GuestUser());
		if(parking_spot!= null)
			parking_spot.assignParkingSpot(new GuestUser());
		
		testSearchParkingSpot_util_001(null, new GuestUser(), false);
	}
	
	@Test
	public void testSearchParkingSpot_006() {
		ParkingSpot parking_spot= parked_users.searchParkingSpot(new HandicappedUser());
		if(parking_spot!= null)
			parking_spot.assignParkingSpot(new HandicappedUser());
		
		testSearchParkingSpot_util_001("226", new HandicappedUser(), true);
	}

	/*@Test
	public void testAddParkingUser() {
		fail("Not yet implemented");
	}

	@Test
	public void testRemoveParkedUser() {
		fail("Not yet implemented");
	}

	@Test
	public void testSearchBySpotNumber() {
		fail("Not yet implemented");
	}*/

}
